home *** CD-ROM | disk | FTP | other *** search
- #define __USE_SYSBASE 1
- #include <clib/alib_protos.h>
- #include <exec/alerts.h>
- #include <exec/execbase.h>
- #include <exec/memory.h>
- #include <intuition/intuitionbase.h>
- #include <libraries/cybergraphics.h>
- #include <proto/commodities.h>
- #include <proto/cybergraphics.h>
- #include <proto/dos.h>
- #include <proto/exec.h>
- #include <proto/intuition.h>
- #include <proto/icon.h>
- #include <proto/utility.h>
- #include <workbench/startup.h>
- #include <string.h>
-
-
- /* Compiler specific stuff. */
- #define SAVEDS __saveds
- #define ASM __asm
- #define REG(x) register __ ## x
- #define STKARGS __stdargs
-
- #define VERSION "1.0"
- #define DATE "9.5.97"
-
-
- /******************** Global variables ********************/
-
-
- struct NewBroker NewBroker =
- {
- NB_VERSION,
- "CGXDPMS",
- "CGXDPMS " VERSION "by Magnus Holmgren",
- "DPMS manager for CyberGraphX",
- NBU_UNIQUE, 0, 0,
- NULL, 0
- };
-
- struct Library *CxBase;
- struct Library *CyberGfxBase;
- struct DosLibrary *DOSBase;
- struct Library *IconBase;
- struct IntuitionBase *IntuitionBase;
- struct ExecBase *SysBase;
- struct Library *UtilityBase;
-
- struct MsgPort *CxPort;
- struct WBStartup *WBMsg;
- CxObj *Broker, *Sender, *Custom;
-
- LONG StandbyTime, SuspendTime, OffTime, IETime;
- LONG StandbyCounter, SuspendCounter, OffCounter;
- LONG SendShift, NoMouse, State, FinalState;
-
- struct InputEvent ShiftDown, ShiftUp;
-
-
- #define DEF_CXPRI 1
- #define DEF_STANDBY 20
- #define DEF_SUSPEND 20
- #define DEF_OFF 20
- #define DEF_SENDSHIFT 1
-
- #define ID_SENDER 49
- #define ID_CUSTOM 17
- #define MAGIC ( APTR ) 87654321L
-
- struct Args
- {
- LONG *CxPriority;
- LONG *StandbyTime;
- LONG *SuspendTime;
- LONG *OffTime;
- LONG *ShiftTime;
- LONG SendShift;
- LONG NoMouse;
- };
-
- #define TEMPLATE "CX_PRIORITY/K/N,STANDBYTIME/K/N,SUSPENDTIME/K/N,OFFTIME/K/N,SHIFTTIME/K/N,SENDSHIFT/S,NOMOUSE/S"
-
-
- /******************** Startup code ********************/
-
-
- static LONG Main( VOID );
-
-
- SAVEDS LONG
- Startup( VOID )
- {
- LONG r;
-
- SysBase = *( ( struct ExecBase ** ) 4 );
-
- {
- struct Process *thisTask = ( struct Process * ) FindTask( NULL );
-
- if( !thisTask->pr_CLI )
- {
- /* Handle Workbench startup message */
- struct MsgPort *port = &thisTask->pr_MsgPort;
-
- WaitPort( port );
- WBMsg = ( struct WBStartup * ) GetMsg( port );
- }
- }
-
- SetSignal( 0, SIGBREAKF_CTRL_C );
-
- if( SysBase->LibNode.lib_Version >= 37 )
- {
- r = Main();
- }
- else
- {
- r = 100;
- }
-
- if( WBMsg )
- {
- Forbid();
- ReplyMsg( ( struct Message * ) WBMsg );
- }
-
- return( r );
- }
-
-
- /******************** String constants ********************/
-
-
- static const TEXT Ver[] = "$VER: CGXDPMS " VERSION " (" DATE ")";
-
-
- /******************** Misc ********************/
-
-
- static LONG
- MyRequest( STRPTR title, STRPTR body, STRPTR gads, ... )
- {
- struct EasyStruct es;
-
- es.es_StructSize = sizeof( es );
- es.es_Flags = 0;
- es.es_Title = title;
- es.es_TextFormat = body;
- es.es_GadgetFormat = gads;
- return( EasyRequestArgs( NULL, &es, NULL, &gads + 1 ) );
- }
-
-
- static VOID
- ErrRequest( STRPTR body, ... )
- {
- if( WBMsg )
- {
- MyRequest( "CGXDPMS error message", body, "Quit", &body + 1 );
- }
- else
- {
- VPrintf( body, &body + 1 );
- }
- }
-
-
- /******************** Libs ********************/
-
-
- static struct Library *
- OpenLib( STRPTR name, LONG ver )
- {
- struct Library *lib;
-
- if( !( lib = OpenLibrary( name, ver ) ) )
- {
- ErrRequest( "Couldn't open %s\nversion %ld or higher!", name, ver );
- }
-
- return( lib );
- }
-
-
- #define CloseLib(lib) CloseLibrary( ( struct Library * ) lib )
-
-
- static VOID
- CloseLibs( VOID )
- {
- if( DOSBase )
- {
- CloseLib( DOSBase );
- CloseLib( IntuitionBase );
- CloseLib( UtilityBase );
- CloseLib( CyberGfxBase );
- CloseLib( CxBase );
- }
- }
-
-
- static BOOL
- OpenLibs( VOID )
- {
- BOOL rc = FALSE;
-
- if( DOSBase = ( struct DosLibrary * ) OpenLibrary( "dos.library", 37 ) )
- {
- if( IntuitionBase = ( struct IntuitionBase * ) OpenLibrary( "intuition.library", 37 ) )
- {
- if( ( UtilityBase = OpenLib( "utility.library", 37 ) )
- && ( CyberGfxBase = OpenLib( "cybergraphics.library", 40 ) )
- && ( CxBase = OpenLib( "commodities.library", 37 ) ) )
- {
- rc = TRUE;
- }
- }
- else
- {
- Alert( AT_Recovery | AN_Unknown | AG_OpenLib | AO_Intuition );
- }
- }
- else
- {
- Alert( AT_Recovery | AN_Unknown | AG_OpenLib | AO_DOSLib );
- }
-
- return( rc );
- }
-
-
- /******************** Argument parsing ********************/
-
-
- static LONG
- GetTimeTT( const struct DiskObject *icon, STRPTR name, LONG def )
- {
- STRPTR str;
- LONG val;
-
- val = def;
-
- if( str = FindToolType( icon->do_ToolTypes, name ) )
- {
- if( StrToLong( str, &val ) == -1 )
- {
- MyRequest( "CGXDMPS Warning", "Argument for %s should be numeric.\nUsing default (%ld).", name, def );
- val = def;
- }
- }
-
- return( SMult32( val, 60 ) );
- }
-
-
- static BOOL
- ParseWBArgs( VOID )
- {
- BOOL rc = FALSE;
-
- if( IconBase = OpenLib( "icon.library", 37 ) )
- {
- struct DiskObject *icon;
- BPTR oldDir;
-
- oldDir = CurrentDir( WBMsg->sm_ArgList[ 0 ].wa_Lock );
-
- /* Lazy parsing: Ignore any multiselected icons... */
- if( icon = GetDiskObject( WBMsg->sm_ArgList[ 0 ].wa_Name ) )
- {
- NewBroker.nb_Pri = GetTimeTT( icon, "CX_PRIORITY", DEF_CXPRI );
- StandbyTime = GetTimeTT( icon, "STANDBYTIME", DEF_STANDBY );
- SuspendTime = GetTimeTT( icon, "SUSPENDTIME", DEF_SUSPEND );
- OffTime = GetTimeTT( icon, "OFFTIME", DEF_OFF );
- IETime = GetTimeTT( icon, "SHIFTTIME", DEF_SENDSHIFT );
- SendShift = ( LONG ) FindToolType( icon->do_ToolTypes, "SENDSHIFT" );
- NoMouse = ( LONG ) FindToolType( icon->do_ToolTypes, "NOMOUSE" );
- rc = TRUE;
-
- FreeDiskObject( icon );
- }
- else
- {
- ErrRequest( "Couldn't get program icon!" );
- }
-
- CurrentDir( oldDir );
- CloseLibrary( IconBase );
- }
- else
- {
- ErrRequest( "Couldn't open icon.library\nversion 37 or higher!" );
- }
-
- return( rc );
- }
-
-
- static LONG
- GetTime( LONG *val, LONG def )
- {
- LONG rc;
-
- rc = def;
-
- if( val )
- {
- rc = *val;
- }
-
- return( SMult32( rc, 60 ) );
- }
-
-
- static BOOL
- ParseCLIArgs( VOID )
- {
- struct Args args;
- struct RDArgs *rdarg;
- BOOL rc = FALSE;
-
- memset( &args, 0, sizeof( args ) );
-
- if( rdarg = ReadArgs( TEMPLATE, ( LONG * ) &args, NULL ) )
- {
- NewBroker.nb_Pri = GetTime( args.CxPriority, DEF_CXPRI );
- StandbyTime = GetTime( args.StandbyTime, DEF_STANDBY );
- SuspendTime = GetTime( args.SuspendTime, DEF_SUSPEND );
- OffTime = GetTime( args.OffTime, DEF_OFF );
- IETime = GetTime( args.ShiftTime, DEF_SENDSHIFT );
- SendShift = args.SendShift;
- NoMouse = args.NoMouse;
- rc = TRUE;
-
- FreeArgs( rdarg );
- }
-
- return( rc );
- }
-
-
- static BOOL
- ParseArgs( VOID )
- {
- return( ( BOOL ) ( WBMsg ? ParseWBArgs() : ParseCLIArgs() ) );
- }
-
-
- /******************** Commodity support ********************/
-
-
- /* This function runs on the input.device task context. Thus, we need to
- * set smalldata base, make sure we don't call any nasty functions, and
- * generally try to do our job quickly.
- */
- static SAVEDS STKARGS VOID
- CxCustomFunc( register CxMsg *msg, CxObj *obj )
- {
- struct InputEvent *ie;
- static LONG LastSecs, LastIE;
- LONG diff;
-
- ie = ( struct InputEvent * ) CxMsgData( msg );
-
- switch( ie->ie_Class )
- {
- case IECLASS_RAWMOUSE:
- case IECLASS_POINTERPOS:
- case IECLASS_NEWPOINTERPOS:
- if( NoMouse && ( ie->ie_Code == IECODE_NOBUTTON ) )
- {
- /* Ignore mouse movements */
- break;
- }
-
- case IECLASS_RAWKEY:
- if( ie->ie_position.ie_addr == MAGIC )
- {
- /* Ignore rawkeys we send out */
- break;
- }
-
- case IECLASS_DISKREMOVED:
- case IECLASS_DISKINSERTED:
- StandbyCounter = StandbyTime;
- SuspendCounter = SuspendTime;
- OffCounter = OffTime;
-
- if( State != DPMS_ON )
- {
- State = DPMS_ON;
- RouteCxMsg( msg, Sender );
- }
-
- break;
-
- case IECLASS_TIMER:
- diff = ie->ie_TimeStamp.tv_secs - LastSecs;
-
- if( ( diff > 0 ) && ( State != FinalState ) && LastSecs )
- {
- if( ( State < DPMS_STANDBY ) && ( StandbyCounter > 0 ) )
- {
- StandbyCounter -= diff;
-
- if( StandbyCounter <= 0 )
- {
- State = DPMS_STANDBY;
- RouteCxMsg( msg, Sender );
- }
- }
- else if( ( State < DPMS_SUSPEND ) && ( SuspendCounter > 0 ) )
- {
- SuspendCounter -= diff;
-
- if( SuspendCounter <= 0 )
- {
- State = DPMS_SUSPEND;
- RouteCxMsg( msg, Sender );
- }
- }
- else if( ( State < DPMS_OFF ) && ( OffCounter > 0 ) )
- {
- OffCounter -= diff;
-
- if( OffCounter <= 0 )
- {
- State = DPMS_OFF;
- RouteCxMsg( msg, Sender );
- }
- }
-
- if( SendShift && ( State > DPMS_ON ) )
- {
- diff = ie->ie_TimeStamp.tv_secs - LastIE;
-
- if( diff > IETime )
- {
- LastIE = ie->ie_TimeStamp.tv_secs;
- ShiftDown.ie_TimeStamp = ie->ie_TimeStamp;
- ShiftUp.ie_TimeStamp = ie->ie_TimeStamp;
-
- /* Hm.. Maybe this would be better to do on the
- * main process' context. Oh well, not called
- * often anyway. ;)
- */
- AddIEvents( &ShiftDown );
- }
- }
- }
-
- LastSecs = ie->ie_TimeStamp.tv_secs;
- break;
- }
- }
-
-
- static VOID
- FreeBroker( VOID )
- {
- DeleteCxObjAll( Broker );
- DeleteMsgPort( CxPort );
- }
-
-
- static BOOL
- InitBroker( VOID )
- {
- BOOL rc = FALSE;
-
- ShiftUp.ie_Class = ShiftDown.ie_Class = IECLASS_RAWKEY;
- ShiftDown.ie_Code = 0x60,
- ShiftUp.ie_Code = IECODE_UP_PREFIX | 0x60;
- ShiftUp.ie_position.ie_addr = ShiftDown.ie_position.ie_addr = MAGIC;
- ShiftDown.ie_NextEvent = &ShiftUp;
-
- StandbyCounter = StandbyTime;
- SuspendCounter = SuspendTime;
- OffCounter = OffTime;
- State = DPMS_ON;
-
- if( StandbyTime )
- {
- FinalState = DPMS_STANDBY;
- }
- else if( SuspendTime )
- {
- FinalState = DPMS_SUSPEND;
- }
- else
- {
- FinalState = DPMS_OFF;
- }
-
- if( CxPort = NewBroker.nb_Port = CreateMsgPort() )
- {
- LONG err;
-
- if( Broker = CxBroker( &NewBroker, &err ) )
- {
- AttachCxObj( Broker, Custom = CxCustom( CxCustomFunc, ID_CUSTOM ) );
- AttachCxObj( Custom, Sender = CxSender( CxPort, ID_SENDER ) );
-
- if( CxObjError( Broker ) || CxObjError( Custom ) )
- {
- ErrRequest( "Not enough memory for Commodities objects!" );
- }
- else
- {
- rc = TRUE;
- }
- }
- else if( err != CBERR_DUP )
- {
- ErrRequest( "Couldn't create broker!" );
- }
- }
- else
- {
- ErrRequest( "Couldn't create message port!" );
- }
-
- if( !rc )
- {
- FreeBroker();
- }
-
- return( rc );
- }
-
-
- static VOID
- HandleEvent( VOID )
- {
- struct Screen *wb;
-
- /* Configurable screen name? Maybe for 1.1... */
- if( wb = LockPubScreen( "Workbench" ) )
- {
- /* Passing args via globals isn't the best perhaps, but it works. ;) */
- CVideoCtrlTags( &wb->ViewPort,
- SETVC_DPMSLevel, State,
- TAG_DONE );
-
- UnlockPubScreen( NULL, wb );
- }
- }
-
-
- static BOOL
- HandleCxPort( VOID )
- {
- CxMsg *msg;
- BOOL run = TRUE;
-
- while( msg = ( CxMsg * ) GetMsg( CxPort ) )
- {
- LONG id, type;
-
- id = CxMsgID( msg );
- type = CxMsgType( msg );
- ReplyMsg( ( struct Message * ) msg );
-
- switch( type )
- {
- case CXM_IEVENT:
- HandleEvent();
- break;
-
- case CXM_COMMAND:
- switch( id )
- {
- case CXCMD_DISABLE:
- ActivateCxObj( Broker, FALSE );
- break;
-
- case CXCMD_ENABLE:
- ActivateCxObj( Broker, TRUE );
- break;
-
- case CXCMD_KILL:
- run = FALSE;
- break;
- }
-
- break;
- }
- }
-
- return( run );
- }
-
-
- /******************** Main program ********************/
-
-
- static VOID
- MainLoop( VOID )
- {
- LONG cxMask = 1 << CxPort->mp_SigBit;
- BOOL run = TRUE;
-
- ActivateCxObj( Broker, TRUE );
-
- while( run )
- {
- LONG sigs;
-
- sigs = Wait( cxMask | SIGBREAKF_CTRL_C );
-
- if( sigs & cxMask )
- {
- if( !HandleCxPort() )
- {
- run = FALSE;
- }
- }
-
- if( sigs & SIGBREAKF_CTRL_C )
- {
- run = FALSE;
- }
- }
- }
-
-
- static LONG
- Main( VOID )
- {
- LONG ret = RETURN_FAIL;
-
- if( OpenLibs() )
- {
- if( ParseArgs() )
- {
- if( InitBroker() )
- {
- MainLoop();
- ret = RETURN_OK;
-
- FreeBroker();
- }
- }
-
- CloseLibs();
- }
-
- return( ret );
- }
-